using System;
using System.Collections.Generic;
using System.IO;
using System.Threading.Tasks;
using Avalonia;
using Microsoft.Extensions.Logging;
using JMClient.Tools;

namespace JMClient.Service;

/// <summary>
/// 配置服务接口 - 专注于文件读写和资源管理
/// </summary>
public interface IConfigurationService
{
    T? LoadConfigurationFromFile<T>(string filePath) where T : class, new();
    Task<T?> LoadConfigurationFromFileAsync<T>(string filePath) where T : class, new();
    bool SaveConfigurationToFile(object configuration, string filePath);
    Task<bool> SaveConfigurationToFileAsync(object configuration, string filePath);
    bool ValidateConfigurationFile(string filePath);
    void LoadConfigurationToResources(object configuration);
    void LoadConfigurationToResources(object configuration, string section);
    void UpdateResource(string resourceKey, object value);
    T? GetResource<T>(string resourceKey);
    void RefreshResources();
    void ClearResources();
}

/// <summary>
/// 配置服务实现 - 专注于文件读写和资源管理
/// </summary>
public class ConfigurationService : IConfigurationService
{
    private readonly ILogger<ConfigurationService> _logger;
    private readonly Dictionary<string, object> _resources = new();

    /// <summary>
    /// ConfigurationService的构造方式 依赖注入
    /// </summary>
    /// <param name="logger"></param>
    public ConfigurationService(ILogInstance logger)
    {
        _logger = LogManagement.GetLogger<ConfigurationService>(logger.GetType());
        _logger.LogInformation("ConfigurationService 初始化完成");
    }

    /// <summary>
    /// 从文件加载配置
    /// </summary>
    public T? LoadConfigurationFromFile<T>(string filePath) where T : class, new()
    {
        try
        {
            if (!File.Exists(filePath))
            {
                _logger.LogWarning("配置文件不存在: {FilePath}", filePath);
                return new T();
            }

            var result = JsonHelper.LoadFromFile<T>(filePath, _logger);
            _logger.LogInformation("成功从文件加载配置: {FilePath}", filePath);
            return result;
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "从文件加载配置失败: {FilePath}", filePath);
            return new T();
        }
    }

    /// <summary>
    /// 异步从文件加载配置
    /// </summary>
    public async Task<T?> LoadConfigurationFromFileAsync<T>(string filePath) where T : class, new()
    {
        try
        {
            if (!File.Exists(filePath))
            {
                _logger.LogWarning("配置文件不存在: {FilePath}", filePath);
                return new T();
            }

            var result = await Task.Run(() => JsonHelper.LoadFromFile<T>(filePath, _logger));
            _logger.LogInformation("成功从文件异步加载配置: {FilePath}", filePath);
            return result;
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "从文件异步加载配置失败: {FilePath}", filePath);
            return new T();
        }
    }

    /// <summary>
    /// 保存配置到文件
    /// </summary>
    public bool SaveConfigurationToFile(object configuration, string filePath)
    {
        try
        {
            var result = JsonHelper.SaveToFile(configuration, filePath, _logger);
            if (result)
            {
                _logger.LogInformation("成功保存配置到文件: {FilePath}", filePath);
            }
            return result;
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "保存配置到文件失败: {FilePath}", filePath);
            return false;
        }
    }

    /// <summary>
    /// 异步保存配置到文件
    /// </summary>
    public async Task<bool> SaveConfigurationToFileAsync(object configuration, string filePath)
    {
        try
        {
            var result = await Task.Run(() => JsonHelper.SaveToFile(configuration, filePath, _logger));
            if (result)
            {
                _logger.LogInformation("成功异步保存配置到文件: {FilePath}", filePath);
            }
            return result;
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "异步保存配置到文件失败: {FilePath}", filePath);
            return false;
        }
    }

    /// <summary>
    /// 验证配置文件
    /// </summary>
    public bool ValidateConfigurationFile(string filePath)
    {
        try
        {
            if (!File.Exists(filePath))
            {
                _logger.LogWarning("配置文件不存在: {FilePath}", filePath);
                return false;
            }

            var jsonContent = File.ReadAllText(filePath);
            var isValid = JsonHelper.IsValidJson(jsonContent);
            _logger.LogInformation("配置文件验证结果: {FilePath}, 有效: {IsValid}", filePath, isValid);
            return isValid;
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "验证配置文件失败: {FilePath}", filePath);
            return false;
        }
    }

    /// <summary>
    /// 将配置加载到资源字典
    /// </summary>
    public void LoadConfigurationToResources(object configuration)
    {
        try
        {
            var properties = configuration.GetType().GetProperties();
            foreach (var property in properties)
            {
                var value = property.GetValue(configuration);
                if (value != null)
                {
                    var resourceKey = property.Name;
                    UpdateResource(resourceKey, value);
                }
            }
            _logger.LogInformation("成功将配置加载到资源字典");
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "将配置加载到资源字典失败");
        }
    }

    /// <summary>
    /// 将配置加载到资源字典（指定节）
    /// </summary>
    public void LoadConfigurationToResources(object configuration, string section)
    {
        try
        {
            var properties = configuration.GetType().GetProperties();
            foreach (var property in properties)
            {
                var value = property.GetValue(configuration);
                if (value != null)
                {
                    var resourceKey = $"{section}.{property.Name}";
                    UpdateResource(resourceKey, value);
                }
            }
            _logger.LogInformation("成功将配置节加载到资源字典: {Section}", section);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "将配置节加载到资源字典失败: {Section}", section);
        }
    }

    /// <summary>
    /// 更新资源
    /// </summary>
    public void UpdateResource(string resourceKey, object value)
    {
        try
        {
            _resources[resourceKey] = value;
            
            // 同时更新到 Avalonia 资源字典
            if (Application.Current?.Resources != null)
            {
                Application.Current.Resources[resourceKey] = value;
            }
            
            _logger.LogDebug("成功更新资源: {ResourceKey}", resourceKey);
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "更新资源失败: {ResourceKey}", resourceKey);
        }
    }

    /// <summary>
    /// 获取资源
    /// </summary>
    public T? GetResource<T>(string resourceKey)
    {
        try
        {
            // 首先从内部资源字典获取
            if (_resources.TryGetValue(resourceKey, out var value) && value is T typedValue)
            {
                return typedValue;
            }

            // 然后从 Avalonia 资源字典获取
            if (Application.Current?.Resources.TryGetValue(resourceKey, out var avaloniaValue) == true && avaloniaValue is T typedAvaloniaValue)
            {
                return typedAvaloniaValue;
            }

            _logger.LogDebug("资源未找到: {ResourceKey}", resourceKey);
            return default;
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "获取资源失败: {ResourceKey}", resourceKey);
            return default;
        }
    }

    /// <summary>
    /// 刷新资源
    /// </summary>
    public void RefreshResources()
    {
        try
        {
            // 重新加载所有资源到 Avalonia 资源字典
            foreach (var kvp in _resources)
            {
                if (Application.Current?.Resources != null)
                {
                    Application.Current.Resources[kvp.Key] = kvp.Value;
                }
            }
            _logger.LogInformation("成功刷新资源字典");
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "刷新资源字典失败");
        }
    }

    /// <summary>
    /// 清除资源
    /// </summary>
    public void ClearResources()
    {
        try
        {
            _resources.Clear();
            _logger.LogInformation("成功清除资源字典");
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "清除资源字典失败");
        }
    }
} 